
/**
 * 事件管理系统
 */
class ClientEvent {

    /**
     * @type {Map<string,Array<{func:Function,_this:object,once:boolean}>>}
     */
    events = new Map();
    /**
     * 
     * @param {any} eventName 
     * @param {Array<any>} args 
     */
    async dispatchEvent (eventName, args) {
        await 1
        if (!this.events.has(eventName)) {
            return
        }

        const list = this.events.get(eventName)
        list.forEach(item => {
            if (args) {
                item.func.call(item._this, ...args)
            } else {
                item.func.call(item._this)
            }
        })
        this.events.set(eventName, list.filter(item => item.once == false))
    }
    /**
     * @param {any} eventName 
     * @param {Function} func 
     */
    on (eventName, func, target) {
        if (!this.events.has(eventName)) {
            this.events.set(eventName, [])
        }
        this.events.get(eventName).push({
            _this: target,
            func,
            once: false
        })
    }
    /**
     * @param {any} eventName 
     * @param {Function} func 
     */
    off (eventName, func, target) {
        if (!eventName) {
            console.error("参数没有eventName")
            return
        }
        if (this.events.has(eventName)) {
            if (func && target) {
                this.events.set(eventName, this.events.get(eventName).filter(item => !(item.func === func && item._this === target)))
            } else if (func) {
                this.events.set(eventName, this.events.get(eventName).filter(item => !(item.func === func)))
            } else {
                this.events.set(eventName, this.events.get(eventName).filter(() => false))
            }
        }
    }
    /**
     * @param {any} eventName 
     * @param {Function} func 
     */
    once (eventName, func, target) {
        if (!this.events.has(eventName)) {
            this.events.set(eventName, [])
        }
        this.events.get(eventName).push({
            _this: target,
            func,
            once: true
        })
    }
    listEvents () {
        for (let key of this.events.keys()) {
            console.log(this.events.get(key))
        }
    }
}

// module.exports.clientEvent = new ClientEvent

export const clientEvent = new ClientEvent
